<template>
  <div class="container">
    <el-card>
      <el-form
        ref="topForm"
        :model="form"
        @submit.native.prevent
      >
        <div style="display: flex; justify-content: space-between;">
          <span>
            <el-form-item prop="idNum" style="display: inline-block; width: 300px; margin-right: 12px; margin-bottom: 0;">
              <el-input v-model.trim="form.searchParam" clearable placeholder="流水号/付款方名称/付款方账号" />
            </el-form-item>
            <el-button type="primary" icon="el-icon-search" style="margin-right: 12px" @click="queryCashBackList">查询</el-button>
            <el-form-item prop="idNum" style="display: inline-block; margin-right: 12px; margin-bottom: 0;">
              <el-radio-group v-model="form.claimStatus" style="width: 100%;" @change="changClaimStatus">
                <el-radio-button v-for="(item, index) in typeList" :key="index" :label="item.value">{{ item.label }}</el-radio-button>
              </el-radio-group>
            </el-form-item>
          </span>
          <span>
            <el-button v-permission="['f02_01']" type="primary" @click="importFlowVisible = true">导入银行流水</el-button>
          </span>
        </div>
      </el-form>
    </el-card>
    <el-card style="margin-top: 12px;">
      <BaseTable
        ref="cashBackPoolTable"
        :table-data="tableData"
        :table-list="tableList"
        :total="total"
        :loading="cashBackListLoading"
        show-index
        show-pagination
        @pagination="handlePagination"
      >
        <el-table-column
          fixed="right"
          label="操作"
          width="110px"
        >
          <template v-slot="scope">
            <el-button v-permission="['f02_02']" type="text" :disabled="getEditStatus(scope.row.claimStatus, scope.row.writeOffStatus)" @click="editCashBack(scope.row.id)">编辑</el-button>
            <el-button v-permission="['f02_03']" type="text" @click="record(scope.row.id)">认领记录</el-button>
          </template>
        </el-table-column>
      </BaseTable>
    </el-card>
    <el-dialog
      width="800px"
      :visible.sync="visible"
      :close-on-press-escape="false"
      @open="openCashBackDetailDialog"
    >
      <template slot="title">
        <div class="d-flex justify-content-center">编辑收款流水</div>
      </template>
      <el-form
        ref="ruleForm"
        v-loading="cashBackDetailLoading"
        :model="editData"
        :rules="editDataRules"
      >
        <el-form-item label="水单金额：" prop="bankSlipAmount" label-width="150px">
          <span>{{ `${editData.bankSlipAmount} ${getDictionaryLabel(editData.bankSlipCurrency, currency)}` }}</span>
        </el-form-item>
        <el-form-item label="水单附件：" prop="attachmentList" label-width="150px">
          <div class="d-flex flex-column">
            <el-button
              v-for="(item, index) in editData.attachmentList"
              :key="index"
              type="text"
              style="margin: 0"
              class="text-left"
              @click="previewHandle(item.attachmentUrl, item.filename)"
            >{{ item.filename }}</el-button>
          </div>

        </el-form-item>
        <el-form-item label="认领客户：" prop="finalCompanyId" label-width="150px">
          <div style="display: flex;">
            <el-select
              v-model="editData.finalCompanyId"
              v-loadmore="loadmoreCompany"
              placeholder="请输入认领客户"
              clearable
              filterable
              remote
              :loading="compamyLoading"
              :remote-method="remoteCompany"
              style="width: 100%;"
              @change="changeCompany"
            >
              <el-option
                v-for="item in companyList"
                :key="item.id"
                :value="item.id"
                :label="item.companyNameForeign"
              />
            </el-select>
          </div>
        </el-form-item>
        <el-form-item prop="name" label-width="150px">
          <el-row>
            <el-col :span="8">销售经理：{{ formatUserName(editData.belongUserName) }}</el-col>
            <el-col :span="8">客户类型：{{ getDictionaryLabel(editData.companyTypeCode, company_type) }}</el-col>
            <el-col :span="8">国家：{{ getDictionaryLabel(editData.countryCode, country_code) }}</el-col>
          </el-row>
        </el-form-item>
        <el-form-item label="收款主体：" prop="finalPayeeId" label-width="150px">
          <div style="display: flex;">
            <el-select
              v-model="editData.finalPayeeId"
              style="width: 100%;"
              placeholder="请选择收款主体"
              @change="finalPyeeHandle"
            >
              <el-option
                v-for="item in payeeAccountList"
                :key="item.id"
                :value="item.id"
                :label="item.label"
              />
            </el-select></div>
        </el-form-item>
        <el-form-item label="收款账号：" prop="finalReceivingBankAccount" label-width="150px">
          <div style="display: flex;">
            <el-select
              v-model="editData.finalReceivingBankAccount"
              style="width: 100%;"
              placeholder="请选择收款账号"
              @change="bankAccountHandle"
            >
              <el-option
                v-for="item in bankAccountList"
                :key="item.id"
                :value="item.receivingBankAccount"
                :label="item.label"
              />
            </el-select>
          </div>
        </el-form-item>
        <el-form-item label="金额：" prop="finalAmount" label-width="150px">
          <el-input v-model.trim="editData.finalAmount" placeholder="请输入入账金额" />
        </el-form-item>
        <el-form-item label="水单：" label-width="150px">
          <PublicUpload
            :file-list="uploadAttachmentList"
            :limit="1"
            :largest-size="15"
            :show-file-list="isShowFileList"
            @setFileList="setFileListHandle"
          />
        </el-form-item>
        <el-form-item label="备注：" prop="remark" label-width="150px">
          <div style="display: flex;">
            <el-input
              v-model="editData.remark"
              type="textarea"
              resize="none"
              placeholder="请输入备注"
              maxlength="500"
              show-word-limit
              :rows="5"
            />
          </div>
        </el-form-item>
        <div style="display: flex; justify-content: center;">
          <el-button :loading="confirmLoading" type="primary" @click="submitEditData('ruleForm')">确认</el-button>
          <el-button @click="visible = false">取消</el-button>
        </div>
      </el-form>
    </el-dialog>
    <el-dialog
      title="认领记录"
      width="800px"
      :visible.sync="recordVisible"
      :close-on-press-escape="false"
    >
      <BaseTable
        :table-data="recordList"
        :table-list="tableListForRecord"
        :total="recordTotal"
        :loading="recordListLoading"
        show-index
        show-pagination
        @pagination="handleRecordPagination"
      />
    </el-dialog>
    <el-dialog
      title="导入银行流水"
      class="import-flow"
      width="800px"
      :visible.sync="importFlowVisible"
      :close-on-press-escape="false"
      @open="openImportDialog"
    >
      <el-upload
        ref="importFlow"
        action="#"
        :multiple="false"
        :before-upload="beforeUpload"
        :http-request="httpRequestHandle"
        :on-remove="handleRemove"
        :file-list="fileList"
        :limit="1"
      >
        <el-button slot="trigger" type="primary" style="margin-right: 10px">上传文件</el-button>
        <el-button size="small" type="primary" @click="downLoadTemplate">下载模板</el-button>
      </el-upload>
      <el-divider />
      <div style="color: #F56C6C;">*下载Excel模板，填写数据后，将文件导入</div>
    </el-dialog>
    <BlockDialog v-if="curUrl" :url="curUrl" title="预览" :name="curName" @close="closeHandle" />
  </div>
</template>

<script>
import BaseTable from '@/components/BaseTable'
import BlockDialog from '@/components/BlockDialog'
import {
  cashBackPollList,
  claimList,
  importFlow,
  cashBackDetail,
  payeeAccountList,
  payeeBankList,
  editCashBack
} from '@/service/cashBackPoll'
import PublicUpload from '@/components/PublicUpload'
import { formatTime, getDictionaryLabel, formatMoneyAmount, formatUserName, isSfType } from '@/utils/tools'
import { accountList } from '@/service/accountManage'
import { mapState, mapActions } from 'vuex'

const templateUrl = 'https://data-pudu-test.oss-cn-shenzhen.aliyuncs.com/2022/06/10/85bc79dc-7f3f-4d5e-b35d-777dccbae70f?Expires=4102329600&OSSAccessKeyId=LTAI5tGQjHJzMy6ncBAVJE3j&Signature=D4Tj1cmsNT4danbGd4k6U2XSlsE%3D'

const AmountValidator = (rule, value, callback) => {
  const reg = /^(0|[1-9]\d*)(\.\d+)?$/
  if (value === '') {
    return callback(new Error('请输入入账金额'))
  } else if (!reg.test(value)) {
    return callback(new Error('金额必须为数字'))
  }
  return callback()
}

export default {
  name: 'CashBackPool',
  components: {
    BaseTable,
    PublicUpload,
    BlockDialog
  },
  data() {
    return {
      gutter: 12,
      span: 6,
      curUrl: '',
      curName: '',
      cashBackImportList: [],
      companyList: [],
      getDictionaryLabel,
      formatUserName,
      payeeAccountList: [],
      bankAccountList: [],
      exchangeRate: null,
      compamyLoading: false,
      cashBackDetailLoading: false,
      cashBackListLoading: false,
      recordListLoading: false,
      companyPageData: {
        pageSize: 10,
        pageNum: 1
      },
      companyTotal: 0,
      searchCompanyVal: '',
      form: {
        claimStatus: '',
        searchParam: ''
      },
      typeList: [
        {
          label: '全部状态',
          value: ''
        },
        {
          label: '未认领',
          value: 2
        },
        {
          label: '认领完成',
          value: 5
        }
      ],
      tableData: [],
      tableLoading: false,
      tableList: [
        {
          label: '收款银行',
          prop: 'receivingBankName'
        },
        {
          label: '收款账号',
          prop: 'receivingBankAccount'
        },
        {
          label: '到账时间',
          prop: 'transactionDate',
          width: '134px',
          render: function(node, data) {
            const { row, column: { prop }} = data
            const text = row[prop] ? formatTime(row[prop]) : '-'
            return <span>{{ text }}</span>
          }
        },
        {
          label: '到账金额',
          prop: 'transactionAmount',
          render: (h, data) => {
            const { row, column: { prop }} = data
            const text = row[prop] || row[prop] === 0 ? formatMoneyAmount(row[prop]) : '-'
            return <span>{text}</span>
          }
        },
        {
          label: '交易币种',
          prop: 'transactionCurrency',
          render: (h, data) => {
            const { row, column: { prop }} = data
            const text = this.getDictionaryLabel(row[prop], this.currency)
            return <span>{text}</span>
          }
        },
        {
          label: '流水号',
          prop: 'transactionFlowNo'
        },
        {
          label: '摘要',
          prop: 'summary'
        },
        {
          label: '付款方名称',
          prop: 'payerName',
          width: '200px'
        },
        {
          label: '付款方账号',
          prop: 'payerAccount',
          width: '180px'
        },
        {
          label: '认领状态',
          prop: 'claimStatus',
          render: (node, data) => {
            const { row, column: { prop }} = data
            const text = this.numberStatusText(this.claim_status, row[prop])
            return <span>{ text }</span>
          }
        },
        {
          label: '认领时间',
          prop: 'claimTime',
          width: '134px',
          render: function(node, data) {
            const { row, column: { prop }} = data
            const text = row[prop] ? formatTime(row[prop]) : '-'
            return <span>{ text }</span>
          }
        },
        {
          label: '认领客户',
          prop: 'finalCompanyNameForeign'
        },
        {
          label: '对应水单金额',
          prop: 'bankSlipAmount',
          width: '180px',
          render: (h, data) => {
            const { row, column: { prop }} = data
            const text = row[prop] || row[prop] === 0 ? formatMoneyAmount(row[prop]) : '-'
            return <span>{text}</span>
          }
        },
        {
          label: '水单币种',
          prop: 'bankSlipCurrency',
          render: (h, data) => {
            const { row, column: { prop }} = data
            const text = this.getDictionaryLabel(row[prop], this.currency)
            return <span>{text}</span>
          }
        },
        {
          label: '水单附件',
          prop: 'attachmentList',
          width: '250px',
          render: (h, data) => {
            const { row, column: { prop }} = data
            const arr = row[prop]?.map(ele => {
              return <div style={{ color: 'blue' }}><a onClick={e => this.alinkDownloadAttachment(e, ele.attachmentUrl, ele.filename)}>{ele.filename}</a></div>
            })
            return <div>{arr}</div>
          }
        },
        {
          label: '最终金额',
          prop: 'finalAmount',
          render: (h, data) => {
            const { row, column: { prop }} = data
            const text = row[prop] || row[prop] === 0 ? formatMoneyAmount(row[prop]) : '-'
            return <span>{text}</span>
          }
        },
        {
          label: '最终币种',
          prop: 'finalCurrency',
          render: (h, data) => {
            const { row, column: { prop }} = data
            const text = this.getDictionaryLabel(row[prop], this.currency)
            return <span>{text}</span>
          }
        }
      ],
      pageIndex: 1,
      pageSize: 10,
      total: 0,
      recordTotal: 0,
      recordPageIndex: 1,
      recordPageSize: 10,
      recordId: null,
      visible: false,
      confirmLoading: false,
      isShowFileList: false,
      uploadAttachmentList: [],
      editData: {
        finalCompanyId: '', // 认领客户
        companyNameForeign: '',
        finalPayeeId: '', // 收款主体
        finalReceivingBankAccount: '', // 收款账号
        attachmentList: [], // 附件列表
        finalAmount: '', // 最终金额
        bankSlipAmount: '', // 水单金额
        bankSlipCurrency: '', // 水单币种
        remark: '', // 备注
        belongUserName: '', // 销售经理
        companyTypeCode: '', // 客户类型
        countryCode: '' // 国家
      },
      editDataRules: {
        finalCompanyId: [{ required: true, message: '请选择认领客户', trigger: ['change', 'blur'] }],
        finalPayeeId: [{ required: true, message: '请选择收款主体', trigger: ['change', 'blur'] }],
        finalReceivingBankAccount: [{ required: true, message: '请选择收款账号', trigger: ['change', 'blur'] }],
        finalAmount: [{ required: true, validator: AmountValidator, trigger: 'blur' }]
      },
      recordVisible: false,
      recordList: [], // 认领列表数据
      tableListForRecord: [
        {
          label: '类型',
          prop: 'claimType',
          render: (node, data) => {
            const { row, column: { prop }} = data
            const text = row[prop] === 0 ? '人工认领' : '系统自动认领'
            return <span>{{ text }}</span>
          }
        },
        {
          label: '认领客户',
          prop: 'companyNameForeign'
        },
        {
          label: '认领主体',
          prop: 'payeeName'
        },
        {
          label: '认领人',
          prop: 'claimantName',
          render: (h, data) => {
            const { row, column: { prop }} = data
            const text = formatUserName(row[prop])
            return <span>{{ text }}</span>
          }
        },
        {
          label: '审批人',
          prop: 'approverName'
        },
        {
          label: '水单',
          prop: 'attachmentList',
          width: '250px',
          render: (h, data) => {
            const { row, column: { prop }} = data
            const arr = row[prop]?.map(ele => {
              return <div style={{ color: 'blue' }}><a onClick={e => this.alinkDownloadAttachment(e, ele.attachmentUrl, ele.filename)}>{ele.filename}</a></div>
            })
            return <div>{arr}</div>
          }
        },
        {
          label: '备注',
          prop: 'remark'
        },
        {
          label: '状态',
          prop: 'status',
          render: (node, data) => {
            const { row, column: { prop }} = data
            const text = this.numberStatusText(this.write_status, row[prop])
            return <span>{{ text }}</span>
          }
        }
      ],
      importFlowVisible: false,
      fileList: []
    }
  },
  computed: {
    ...mapState({
      currency: state => state.base.currency,
      country_code: state => state.base.country_code,
      claim_status: state => state.base.claim_status,
      write_status: state => state.base.write_status,
      company_type: state => state.base.company_type
    })
  },
  watch: {
    'editData.finalPayeeId': {
      handler(newVal) {
        this.bankAccountList = []
        if (newVal) {
          this.getBankAccountList(newVal)
        }
      }
    }
  },
  mounted() {
    this.getDictionary()
    this.remoteCompany('')
    this.getPayeeAccountList()
    this.queryCashBackList()
  },
  methods: {
    ...mapActions({ getBaseDataList: 'base/getBaseDataList' }),
    async getCashBackPollList() {
      this.cashBackListLoading = true
      const { records, total } = await cashBackPollList({
        ...this.form,
        pageNum: this.pageIndex,
        pageSize: this.pageSize
      }).finally(() => {
        this.cashBackListLoading = false
      })
      this.total = total
      this.tableData = records
    },
    getDictionary() {
      this.getBaseDataList({ type: 'currency' })
      this.getBaseDataList({ type: 'country_code' })
      this.getBaseDataList({ type: 'claim_status' })
      this.getBaseDataList({ type: 'write_status' })
      this.getBaseDataList({ type: 'company_type' })
    },
    queryCashBackList() {
      this.pageIndex = 1
      this.pageSize = 10
      this.$refs.cashBackPoolTable.pageIndex = 1
      this.$refs.cashBackPoolTable.pageSize = 10
      this.getCashBackPollList()
    },
    changClaimStatus() {
      this.queryCashBackList()
    },
    handlePagination(data) {
      const { pageIndex, pageSize } = data
      this.pageIndex = pageIndex
      this.pageSize = pageSize
      this.getCashBackPollList()
    },
    handleRecordPagination(data) {
      const { pageIndex, pageSize } = data
      this.recordPageIndex = pageIndex
      this.recordPageSize = pageSize
      this.record(this.recordId)
    },
    editCashBack(id) {
      this.visible = true
      this.isShowFileList = false
      this.getCashBackDetail(id)
    },
    async record(id) {
      this.recordVisible = true
      this.recordListLoading = true
      this.recordId = id
      const { records, total } = await claimList({
        transactionFlowId: id,
        pageNum: this.recordPageIndex,
        pageSize: this.recordPageSize
      }).finally(() => { this.recordListLoading = false })
      this.recordTotal = total
      this.recordList = records
    },
    submitEditData(formName) {
      this.$refs[formName].validate(async valid => {
        if (valid) {
          if (!this.isEnablePayee(this.editData.finalPayeeId)) {
            // 表示禁用的情形
            return this.$message({
              type: 'error',
              message: '该主体已经被禁用，不允许编辑'
            })
          }
          this.cashBackDetailLoading = true
          this.confirmLoading = true
          this.editData.attachment = this.uploadAttachmentList && this.uploadAttachmentList[0]
          await editCashBack(this.editData).finally(() => {
            this.cashBackDetailLoading = false
            this.confirmLoading = false
          })
          this.$message({
            type: 'success',
            message: '编辑成功'
          })
          this.getCashBackPollList()
          this.visible = false
        } else {
          return false
        }
      })
    },
    handleRemove(file, fileArr) {
      this.fileList = fileArr
    },
    async httpRequestHandle(data) {
      data = data || {}
      const { file } = data
      const fd = new FormData()
      fd.append('file', file)
      await importFlow(fd)
      this.$message({
        type: 'success',
        message: '导入成功'
      })
      this.importFlowVisible = false
      this.queryCashBackList()
    },
    beforeUpload(file) {
      const fileType = file.name.substring(file.name.lastIndexOf('.') + 1)
      const extension = fileType === 'xls' || fileType === 'xlsx'
      const isLess = file.size / 1024 / 1024 <= 10
      if (!extension) {
        this.$message({
          message: '文件格式不正确，请重新上传!',
          type: 'error'
        })
        return false
      }
      if (!isLess) {
        this.$message({
          message: '文件不能超过10M，请重新上传!',
          type: 'error'
        })
        return false
      }
      return true
    },
    async openImportDialog() {
      this.fileList = []
    },
    async openCashBackDetailDialog() {
      await this.$nextTick()
      this.uploadAttachmentList = []
      this.$refs.ruleForm?.clearValidate()
    },
    async getPayeeAccountList() {
      const param = {
        id: '',
        name: ''
      }
      const arr = await payeeAccountList(param) || []
      this.payeeAccountList = arr.map(it => {
        const text = it.payeeStatus === 1 ? '已启用' : '已禁用'
        return {
          ...it,
          id: it.id,
          label: `${it.payeeName} (${text})`
        }
      })
    },
    async getBankAccountList(payeeAccountId) {
      const param = {
        payeeAccountId
      }
      const result = await payeeBankList(param)
      result.forEach(it => {
        it.label = `${it.receivingBankAccount}(${this.getDictionaryLabel(it.currencyCode, this.currency)})`
      })
      this.bankAccountList = result
      if (this.editData.finalReceivingBankAccount) {
        const item = this.bankAccountList.find(it => it.receivingBankAccount === this.editData.finalReceivingBankAccount) || {}
        this.editData.finalCurrency = item.currencyCode
      }
    },
    remoteCompany(query) {
      this.companyList = []
      this.searchCompanyVal = query
      this.companyPageData.pageNum = 1
      setTimeout(() => {
        this.getCompanyList(query)
      }, 200)
    },
    async getCompanyList(query) {
      this.compamyLoading = true
      const { records, total } = await accountList({ companyNameForeign: query, ...this.companyPageData })
      this.compamyLoading = false
      this.companyTotal = total
      this.companyList = [...this.companyList, ...records]
    },
    loadmoreCompany() {
      if (this.companyList.length >= this.companyTotal) return
      this.companyPageData.pageNum++
      this.getCompanyList('')
    },
    // 获取回款池详情页面数据
    async getCashBackDetail(id) {
      this.cashBackDetailLoading = true
      this.editData = await cashBackDetail({ id }).finally(() => {
        this.cashBackDetailLoading = false
      })
      this.editData.finalAmount = ''
      this.editData.bankSlipAmount = formatMoneyAmount(this.editData.bankSlipAmount)
      this.editData.attachmentList = this.editData.attachmentList || []
      /**
       * 当遇到不是第一页的数据回显的时候
       */
      this.handlerViewCompany(this.editData.finalCompanyId, this.editData.finalCompanyNameForeign)
    },
    downLoadTemplate() {
      window.location.href = templateUrl
    },
    getEditStatus(claimStatus, writeOffStatus) {
      let flag = null
      // 已认领、未核销的状态才可以编辑
      if (claimStatus === 5 && writeOffStatus === 0) {
        flag = false
      } else {
        flag = true
      }
      return flag
    },
    finalPyeeHandle() {
      this.editData.finalReceivingBankAccount = ''
    },
    setFileListHandle(list) {
      this.isShowFileList = true
      this.uploadAttachmentList = list
    },
    // 预览
    previewHandle(curUrl, curName) {
      // SF全部是新建窗口打开
      if (isSfType(curUrl)) {
        window.open(curUrl)
        return
      } else {
        window.location.href = curUrl
      }
    },
    isEnablePayee(id) {
      let flag
      const item = this.payeeAccountList.find(t => t.id === id) || {}
      if (item.payeeStatus === 1) {
        flag = true
      } else {
        flag = false
      }
      return flag
    },
    bankAccountHandle(value) {
      const item = this.bankAccountList.find(t => t.receivingBankAccount === value) || {}
      this.editData.finalCurrency = item.currencyCode
      this.editData.finalAmount = ''
    },
    numberStatusText(list, status) {
      const item = list.find(it => +it.value === +status) || {}
      const text = item.label
      return text
    },
    // 清除url
    closeHandle() {
      this.curUrl = ''
      this.curName = ''
    },
    alinkDownloadAttachment(e, curUrl, curName) {
      e.preventDefault()
      this.previewHandle(curUrl, curName)
    },
    handlerViewCompany(id, name) {
      const item = this.companyList.find(it => it.id === id)
      if (!item) {
        this.companyList.push({
          id,
          companyNameForeign: name
        })
      }
    },
    changeCompany(val) {
      const item = this.companyList.find(it => it.id === val) || {}
      this.editData.belongUserName = item.belongUserName
      this.editData.companyTypeCode = item.companyTypeCode
      this.editData.countryCode = item.countryCode
    }
  }
}
</script>

<style scoped lang="scss">
.container {
  margin: 12px;
  width: calc(100% - 24px);
}
</style>

<style lang="scss">
.import-flow {
  .el-upload-list__item {
    transition: none ;
  }
}
</style>
